package algorithm.middle;

import java.util.*;

/**
 * <a href="https://leetcode.cn/problems/exclusive-time-of-functions/">.有一个cpu，还有一堆任务。cpu一次只能同时运行一个任务。
 * 当一个新任务开始执行时，如果已经有任务在运行，那就暂停这个任务，先跑我这个新的(无论刚才正在执行的任务是否和我是一个类型，强行挤掉){0:start:0}。
 * 当任务结束时，记录运行时间，然后把他送出cpu，然后查看cpu的等待区还有没有任务在等待，有的话继续运行等待的任务。
 * <p>
 * 输入：n = 2, logs = ["0:start:0","1:start:2","1:end:5","0:end:6"]
 * 输出：[3,4]
 * </a>
 */
public class ExclusiveTime636 {


    /**
     * 1
     * ["0:start:0","0:start:1","0:start:2","0:end:3","0:end:4","0:end:5"]
     */
    public static int[] exclusiveTime(int n, List<String> logs) {
        int[] ints = new int[n];
        Stack<long[]> stack = new Stack<>();
        for (String item : logs) {
            int index = Integer.parseInt(item.substring(0, item.indexOf(":")));
            long time = Integer.parseInt(item.substring(item.lastIndexOf(":") + 1));
            long[] thread = {index, time};
            if (item.contains("start")) {
                //如果是start直接入栈
                stack.push(thread);
            } else {
                //如果是end则和出栈元素计算。
                long count = 0;
                long[] pop = stack.pop();
                if (pop[0] == -1) {
                    count = pop[1];
                    pop = stack.pop();
                }
                int difference = (int) (thread[1] - pop[1] + 1 - count);
                //如果stack不为空，则插入间隔时间。
                if (!stack.isEmpty()) {
                    long[] add = {-1, difference + count};
                    if (stack.peek()[0] == -1){
                        add[1] += stack.pop()[1];
                    }
                    stack.push(add);
                }
                ints[(int) pop[0]] += difference;
            }
        }
        return ints;
    }

    public static void main(String[] args) {
        exclusiveTime(1, Arrays.asList("0:start:0", "0:start:2", "0:end:5", "0:start:6", "0:end:6", "0:end:7"));
    }

}
